package com.diaohaiwen.framework.db.generator;

import cn.hutool.core.date.DateUtil;
import com.alibaba.druid.pool.DruidDataSource;
import com.diaohaiwen.framework.db.obj.BaseCUModel;
import com.mybatisflex.annotation.KeyType;
import com.mybatisflex.codegen.Generator;
import com.mybatisflex.codegen.config.ColumnConfig;
import com.mybatisflex.codegen.config.GlobalConfig;
import com.mybatisflex.codegen.config.TableDefConfig;
import com.mybatisflex.codegen.constant.GenTypeConst;
import com.mybatisflex.codegen.dialect.IDialect;
import com.mybatisflex.codegen.generator.GeneratorFactory;
import com.mybatisflex.core.keygen.KeyGenerators;
import com.mybatisflex.core.service.IService;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import lombok.Builder;
import lombok.Getter;
import lombok.SneakyThrows;

import java.io.File;
import java.util.Objects;

@Getter
@Builder
public class MybatisGenerator {

    /**
     * 作者
     */
    private String author;

    /**
     * 数据库URL
     */
    private String url;
    /**
     * 用户名
     */
    private String username;
    /**
     * 密码
     */
    private String password;

    private String[] tables;

    /**
     * 基类
     */
    private Class<?> clazz;


    private boolean enableService;

    private boolean enableImpl;

    private boolean enableController;

    private boolean enableXml;

    public DruidDataSource getDatasource() {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(url);
        dataSource.setUsername(username);
        dataSource.setPassword(password);
        return dataSource;
    }

    public void generate() {
        Generator generator = new Generator(getDatasource()
                , createGlobalConfig(clazz)
                , IDialect.DEFAULT); //使用哪个方言
        GeneratorFactory.registerGenerator(GenTypeConst.ENTITY, new MyEntityGenerator());
        generator.generate();
    }


    @SneakyThrows
    public GlobalConfig createGlobalConfig(Class<?> clazz) {
        GlobalConfig globalConfig = new GlobalConfig();
        globalConfig.setBasePackage(clazz.getPackageName());

        File file = new File(new File(Objects.requireNonNull(clazz.getClassLoader().getResource("")).toURI()).getParentFile().getParentFile(), "src/main/java");
        System.out.println(file);
        globalConfig.setSourceDir(file.getAbsolutePath());


        //设置生成 entity 并启用 Lombok
        globalConfig.setEntityGenerateEnable(true);
        globalConfig.setEntityWithLombok(true);

        //设置生成 mapper
        globalConfig.setMapperGenerateEnable(true);

        globalConfig.getPackageConfig()
                .setEntityPackage(globalConfig.getBasePackage() + ".obj.model");


        // 注释配置
        globalConfig.getJavadocConfig()
                .setAuthor(author)
                .setSince(DateUtil.now());
        // 策略配置
        ColumnConfig idConfig = new ColumnConfig();
        idConfig.setColumnName("id");
        idConfig.setKeyType(KeyType.Generator);
        idConfig.setKeyValue(KeyGenerators.snowFlakeId);
        idConfig.setPrimaryKey(true);

        globalConfig.getStrategyConfig()
                .setColumnConfig(idConfig);
        // Entity 生成配置
        globalConfig.enableEntity()
                .setSuperClass(BaseCUModel.class)
                .setOverwriteEnable(true)
                .setWithLombok(true);

        // Mapper 生成配置
        globalConfig.enableMapper()
                .setOverwriteEnable(true)
                .setOverwriteEnable(true);


        globalConfig.enableTableDef()
                .setOverwriteEnable(true)
                .setPropertiesNameStyle(TableDefConfig.NameStyle.UPPER_CAMEL_CASE)
                .setClassSuffix("Def");

        if (enableService) {
            globalConfig.enableService()
                    .setClassSuffix("Service")
                    .setOverwriteEnable(true)
                    .setSuperClass(IService.class);
        }

        if (enableImpl) {
            globalConfig.enableServiceImpl()
                    .setClassSuffix("Impl")
                    .setOverwriteEnable(true)
                    .setSuperClass(ServiceImpl.class);
        }

        if (enableController) {
            globalConfig.enableController()
                    .setOverwriteEnable(true)
                    .setClassSuffix("Controller");
        }

        return globalConfig;
    }


}
